package CapaPersistencia;


import CapaLogica.GestionResort;
import CapaDatos.Habitacion;
import java.io.FileOutputStream;
import java.io.IOException;
import java.text.ParseException;
import java.util.ArrayList;
import java.util.Iterator;
import java.util.List;
import org.jdom.Document;
import org.jdom.Element;
import org.jdom.JDOMException;
import org.jdom.input.SAXBuilder;
import org.jdom.output.XMLOutputter;



/**
 * Clase de persistencia de implementacion DAO con tecnologia
 * XML para el dominio de Cliente
 *
 */
public class DAOHabitacionXML implements IDAOHabitacion {

    /** variable que contiene la raiz del documento Xml*/

    private Element root;
    /** variable que contiene la localizacion del archivo xml*/

    private String fileLocation = "C:/ArchivosXml/Habitaciones.xml";

    /**
     * constructor por defecto que inicia los valores para trabajar con el documento
     * xml
     */
    public DAOHabitacionXML() {
        try {
            SAXBuilder builder = new SAXBuilder(false);
            Document doc = null;
            doc = builder.build(fileLocation);
            root = doc.getRootElement();
        } catch (JDOMException ex) {
            System.out.println("No se pudo iniciar la operacion por: " + ex.getMessage());
        } catch (IOException ex) {
            System.out.println("No se pudo iniciar la operacion por: " + ex.getMessage());
        }
    }

    /**
     * firma para pasar un objeto de dominio cliente a un elemento entendible
     * por la libreria jdom para dar soporte al trabajo con xml
     * @param cliente objeto cliente a traducir
     * @return objeto tipo element para el xml
     */
    private Element HabitaciontoXmlElement(Habitacion laHabitacion) {
        Element habitacionTrans = new Element("habitacion");
        Element tipoHab = new Element("tipoHab");
        tipoHab.setText(laHabitacion.getTipoHab());
        Element id = new Element("id");
        id.setText(laHabitacion.getID());
        Element area = new Element("area");
        area.setText(laHabitacion.getArea());
        Element edoActual = new Element("edoActual");
        edoActual.setText(laHabitacion.getEdoActual());
        habitacionTrans.addContent(tipoHab);
        habitacionTrans.addContent(id);
        habitacionTrans.addContent(area);
        habitacionTrans.addContent(edoActual);
        return habitacionTrans;
    }

    /**
     * firma para pasar de on objeto de tipo elemento a un objeto de dominio
     * para dar soporte a la aplicacion
     * @param element elemento a traducir
     * @return objeto de dominio cliente
     */
    private Habitacion HabitacionToObject(Element element) throws ParseException {
        Habitacion habitacion = new Habitacion();
        habitacion.setTipoHab(element.getChildText("tipoHab"));
        habitacion.setID((element.getChildText("id")));
        habitacion.setArea(((element.getChildText("area"))));
        habitacion.setEdoActual((element.getChildText("edoActual")));
        return habitacion;
    }


    /**
     * Operacion para guardar en el documento Xml los cambios efectuados
     * @return true si se cumplio la operacion con exito, false en caso contrario
     */
    private boolean updateDocument() {
        try {
            XMLOutputter out = new XMLOutputter();
            FileOutputStream file = new FileOutputStream(fileLocation);
            out.output(root, file);
            file.flush();
            file.close();
            return true;
        } catch (Exception e) {
            System.out.println("error: " + e.getMessage());
            return false;
        }
    }

    /**
     * Operacion que busca un elemento que cumpla con una condicion en el id del xml
     * @param raiz la raiz del documento xml
     * @param dato el dato a comparar para la busqueda del elemento. Debe ser el identificador
     * @return retorna el elemento si existe con la condicion, en caso contrario retorna null
     */
    public static Element buscar(List raiz, String dato) {
        Iterator i = raiz.iterator();
        while (i.hasNext()) {
            Element e = (Element) i.next();
            if (dato.equals(e.getChild("id").getText())) {
                return e;
            }
        }
        return null;
    }

    /**
     * firma para agregar un nuevo cliente
     * @param cliente objeto cliente a agregar
     * @return valor boleano con la condicion de exito
     */
    public boolean agregarHabitacion(Habitacion habitacion) {
        boolean resultado = false;
        root.addContent(HabitaciontoXmlElement(habitacion));
        GestionResort.getLasHabitaciones().agregarElemento(habitacion);
        resultado = updateDocument();
        return resultado;
    }


    /**
     * firma para buscar un cliente
     * @param cedula numero de cedula del cliente a buscar
     * @return objeto cliente con sus datos segun busqueda
     */
    public Habitacion buscarHabitacion(Integer id) {
        Element aux = new Element("habitacion");
        List salones = this.root.getChildren("habitacion");
        while (aux != null) {
            aux = DAOHabitacionXML.buscar(salones, Integer.toString(id));
            if (aux != null) {
                try {
                    return HabitacionToObject(aux);
                } catch (ParseException ex) {
                    System.out.println(ex.getMessage());
                }
            }
        }
        return null;
    }

    /**
     * firma para actualizar un cliente
     * @param cliente objeto cliente a actualizar
     * @return valor boleano con la condicion de exito
     */
    public boolean actualizarHabitacion(Habitacion habitacion) {
        boolean resultado = false;
        Element aux = new Element("habitacion");
        List salones = this.root.getChildren("habitacion");
        while (aux != null) {
            aux = DAOHabitacionXML.buscar(salones, habitacion.getID());
            if (aux != null) {
                salones.remove(aux);
                resultado = updateDocument();
            }
        }

        System.out.println("Lista actualizada");
        GestionResort.getLasHabitaciones().agregarElemento(habitacion);
        agregarHabitacion(habitacion);
        return resultado;
    }

    /**
     * firma para borrar un cliente
     * @param cedula cedula del cliente a borrar
     * @return valor boleano con la condicion de exito
     */
    public boolean borrarHabitacion(Integer cedula) {
        boolean resultado = false;
        Element aux = new Element("habitacion");
        List salones = this.root.getChildren("habitacion");
        while (aux != null) {
            aux = DAOHabitacionXML.buscar(salones, Integer.toString(cedula));
            if (aux != null) {
                salones.remove(aux);
                System.out.println("Lista con elementos borrados");
                GestionResort.getLasHabitaciones().eliminarHabitacionPorCedula(cedula);
                resultado = updateDocument();
            }
        }
        return resultado;
    }

    /**
     * firma para obtener todos los clientes
     * @return ArrayList con todos los objetos cliente
     */
    public ArrayList<Habitacion> todasLasHabitaciones () {
        ArrayList<Habitacion> resultado = new ArrayList<Habitacion>();
        for (Object it : root.getChildren()) {
            Element xmlElem = (Element) it;
            try {
                resultado.add(HabitacionToObject(xmlElem));
            } catch (ParseException ex) {
                System.out.println(ex.getMessage());
            }
        }
        return resultado;
    }



}
